package emulator.shell.GUI.profiling;

import java.util.Collection;

import emulator.hardware.debug.AddressStatistics;
import emulator.hardware.debug.CpuProfiler;
import emulator.hardware.debug.profiling.CodeSegment;
import emulator.shell.GUI.debugger.CodePanel;

public class ProfilingStatisticsPresenter
{
	private CodePanel codePanel = null;
	private ProfilingStatisticsView view = null;
	private String appName;
	
	public ProfilingStatisticsPresenter(String appName, CodePanel codePanel)
	{
		this.appName = appName;
		this.codePanel = codePanel;
	}
	
	public void toggleView()
	{
		if (view == null)
		{
			view = new ProfilingStatisticsView(appName, this);
			view.initView(createViewModel());
			view.restorePosition();
			view.setVisible(true);
		}
		else
		{
			view.toFront();
		}
	}

	private ProfilingStatisticsVM createViewModel()
	{
		ProfilingStatisticsVM profilingStatisticsVM = new ProfilingStatisticsVM();
		
		CpuProfiler profiler = codePanel.getProfiler();
		long totalTicks = 0;
		for (int address = 0; address < 65535; address++)
		{
			AddressStatistics statistics = profiler.getStatisticsForAddress(address);
			if (statistics.getCycleCounter() > 0)
			{
				profilingStatisticsVM.addAddressStatistics(address, statistics.getCycleCounter(), statistics.getExecutionCounter(), codePanel.getLabel(address));
				totalTicks += statistics.getCycleCounter();
			}
			profilingStatisticsVM.setTotalTicks(totalTicks);
		}
		
		Collection<CodeSegment> codeSegments = profiler.getCallGraph().getCodeSegments();
		for (CodeSegment codeSegment : codeSegments)
			profilingStatisticsVM.prepareCodeSegment(codeSegment, codePanel.getLabel(codeSegment.getEnterAddress()));
		for (CodeSegment codeSegment : codeSegments)
			profilingStatisticsVM.processCodeSegment(codeSegment);
		profilingStatisticsVM.addTopLevelSegments(profiler.getCallGraph().getTopLevelSegments(), codePanel);
		
		profilingStatisticsVM.postProcess();
		
		return profilingStatisticsVM;
	}

	public void showCode(int address)
	{
		if (codePanel != null)
			codePanel.showCode(address, true);
	}

	public void onCloseView()
	{
		view = null;
	}

	public void closeView()
	{
		if (view != null)
		{
			view.setVisible(false);
			view = null;
		}
	}

	public void resetStatisticsAndCloseView()
	{
		codePanel.getProfiler().reset();
		closeView();
	}
}
